package com.tian.arch.function.state

import android.view.View
import android.view.ViewGroup


/**
 *  将普通view转换成[StatefulPage]的包装器
 *
 *  下面介绍如何使用这个state框架
 *
 *  ```
 *  1、在Application中初始化Wrapper
 *
 *  PageStateWrapper.init(PageStateConfig(R.layout.loading, R.layout.empty, R.layout.error, pageStateChangeListener)
 *
 *  2、在Activity或者fragment中传入view，这个view通常是activity或fragment的根布局
 *
 *  class Activity .. {
 *      private late var statefulPage:StatefulPage
 *
 *      fun onCreate() {
 *          val rootView = LayoutInflater.from(this).inflate(mLayoutId, null)
 *          statefulPage = PageStateWrapper.default().wrap(rootView)
 *          // 给statefulPage设置retry事件
 *          statefulPage.setRetryAction {
 *              showToast("开始重新加载")
 *          }
 *          setContentView(statefulPage, ViewGroup(-1,-1))
 *      }
 *
 *      // 根据情况再适当的时候调用 StatefulPage的方法进行显示
 *      statefulPage.showContext()
 *      or
 *      statefulPage.showEmptyView()
 *      or
 *      statefulPage.showErrorView()
 *      ...
 *  }
 *
 *  3、如果在某处需要 定制化显示loading之类的，可以如下操作
 *
 *  PageStateWrapper
 *     .default()
 *     .newConfig {
 *        emptyLayout = R.layout.colorfulLoading
 *        ...
 *     }
 *     .wrap(rootView)
 *  ```
 */
class PageStateWrapper(private val config: PageStateConfig) {

    /**
     * 将一个普通的view包装为 拥有状态的page
     */
    fun wrap(view: View): StatefulPage {
        val wrapper = StatefulPage(view.context)
        wrapper.config = this.config
        // 如果view有父容器，那么用 wrapper替换view
        if (view.parent != null) {
            (view.parent as ViewGroup).run {
                val index = indexOfChild(view)
                removeView(view)
                addView(wrapper, index, view.layoutParams)
            }
        }
        wrapper.addView(view, 0)
        return wrapper
    }

    companion object {

        private var globalConfig: PageStateConfig? = null
        private val wrapper by lazy {
            requireNotNull(globalConfig) {
                "You must call 'init' before use"
            }
            PageStateWrapper(globalConfig!!)
        }

        /**
         * 获取全局配置的 PageStateWrapper
         */
        fun default() = wrapper

        /**
         * 初始化全局配置
         */
        fun init(config: PageStateConfig) {
            globalConfig = config
        }

        /**
         *  通过调用本方法, 完成某个页面显示的个性化配置
         *
         *  完成对[StatefulPage]的配置参数[PageStateConfig] 的修改
         */
        fun customConfig(action: PageStateConfig.() -> Unit): PageStateWrapper {
            requireNotNull(globalConfig) {
                "You must call 'init' before use"
            }
            val newConfig = globalConfig?.copy {
                action(this)
                return@copy this
            }
            return PageStateWrapper(newConfig!!)
        }
    }

}



